/*
 * @Author       : xh
 * @Date         : 2022-10-17 14:20:12
 * @LastEditors: y001554
 * @FileName     :
 */
const fsExtra = require('fs-extra')
const path = require('path')
const fs = require('fs')
const inquirer = require('inquirer')
const { defineConfig, build } = require('vite')
const vue = require('@vitejs/plugin-vue')
const vueJsx = require('@vitejs/plugin-vue-jsx')
const nodeprocess = require('child_process')
const root = path.resolve(__dirname, '../../packages')

// console.log(123, path.join(root, '/plugins'))

const baseConfig = defineConfig({
  configFile: false,
  publicDir: false,
  plugins: [vue(), vueJsx()]
})
const rollupOptions = {
  external: ['vue', 'vue-router', 'element-plus'],
  output: {
    globals: {
      vue: 'Vue'
    }
  }
}

// 单组件按需构建
const buildSingle = async (name) => {
  const outputDir = path.join(root, `/${name}/lib`)
  await fsExtra.remove(outputDir)
  console.log('删除旧包', outputDir)
  await build(
    defineConfig({
      ...baseConfig,
      build: {
        rollupOptions,
        lib: {
          entry: path.join(root, `/${name}/index`),
          name: 'index',
          fileName: 'index',
          formats: ['es', 'umd']
        },
        outDir: path.resolve(outputDir)
      }
    })
  )
}

//版本号迭代
const creatVersion = (v, t) => {
  if (!t) return v

  try {
    let [a, b, c] = v.split('.')
    // console.log('answer', a, b, c, t)
    switch (t) {
      case 'major':
        a = +a + 1
        break
      case 'patch':
        b = +b + 1
        break
      default:
        c = +c + 1
        break
    }
    // console.log('answer22', a, b, c)
    return `${a}.${b}.${c}`
  } catch (error) {
    console.log('error', error)
    return null
  }
}

// 生成模块的 package.json 文件
const createPackageJson = async (name, answer) => {
  const rootPackagePath = path.join(root, `/${name}/package.json`)

  fsExtra.readJson(rootPackagePath, (err, obj) => {
    if (err) {
      obj = {}
    }

    const { version = '0.0.0' } = obj

    const newVersion = creatVersion(version, answer.versionType)
    if (!newVersion) {
      throw err
    }
    console.log('version', `${version}==>${newVersion}`)
    obj.type = 'module'
    obj.name = `@loserjohn/${name}`
    obj.main = 'lib/index.umd.js'
    obj.version = newVersion
    obj.module = 'lib/index.js'
    obj.style = 'lib/style.css'
    obj.scripts = {
      mockPublic: 'yalc push',
      public: 'npm publish --access public'
    }
    obj.publishConfig = {
      access: 'public'
    }
    // obj.exports = {
    //   '.': {
    //     import: './lib/index.js',
    //     require: './lib/index.umd.cjs'
    //   }
    // }

    const fileStr = JSON.stringify(obj, '', '\t')

    // 更新外部的json
    fsExtra.outputFileSync(rootPackagePath, fileStr, 'utf-8')

    mockPublich(name)
  })
}

//模拟发布
const mockPublich = async (name) => {
  const src = `pnpm  run -F @loserjohn/${name}  mockPublic`
  console.log('模拟发布', src)
  await nodeprocess.exec(
    `pnpm  run -F @loserjohn/${name}  mockPublic`,
    (err) => {
      if (err) {
        console.log('src', err)
      } else {
        console.log(`${name} 模拟发布成功`)
      }
    }
  )
}

// 获取包组件名称组成的数组
const buildAllPackage = async () => {
  console.log('arguments', process.argv)
  const args = process.argv || []
  const mode = args[args.length - 1] || ''
  let answer = null
  if (mode && mode === '-a') {
    answer = ''
  } else {
    answer = await inquirer.prompt([
      //...
      {
        type: 'list',
        message: '请选择迭代种类',
        name: 'versionType',
        choices: ['minor', 'patch', 'major']
        //、补丁、小改\大改
      }
    ])
  }

  const components = fs.readdirSync(root).filter((name) => {
    const componentDir = path.join(root, name)
    const isDir = fs.lstatSync(componentDir).isDirectory()
    return isDir && fs.readdirSync(componentDir).includes('index.ts')
  })

  // console.log('list', components)
  // 循环一个一个组件构建
  for (const name of components) {
    // 构建单组件
    // 获统一构建
    await buildSingle(name)

    createPackageJson(name, answer)
  }
}

buildAllPackage()
